# !/usr/bin/env python3
# coding=utf8
"""
因为不懂"盈亏分布"图, 所以写了这个代码用于理解,
"""
import collections
import datetime
import numpy
import pandas


def gen_daily_results(count: int = 60) -> dict:
    """"""
    begDate: datetime.date = datetime.date(year=2023, month=1, day=1)
    endDate: datetime.date = begDate+datetime.timedelta(days=count)

    date_s = numpy.arange(start=begDate, stop=endDate)

    net_pnl_s: numpy.ndarray = numpy.random.randint(low=-100, high=+100, size=count)

    assert len(date_s) == len(net_pnl_s)

    daily_results: dict = {}

    for i in range(0, len(net_pnl_s), 1):
        daily_result: dict = {
            "date": date_s[i],
            "net_pnl": net_pnl_s[i],
        }
        daily_results[daily_result["date"]] = daily_result

    return daily_results


def gen_results(daily_results: dict) -> dict:
    """"""
    results: collections.defaultdict = collections.defaultdict(list)

    for daily_result in daily_results.values():
        assert isinstance(daily_result, dict)
        for key, value in daily_result.items():
            results[key].append(value)

    return results


def gen_daily_df(results: dict) -> pandas.DataFrame:
    """"""
    daily_df: pandas.DataFrame = pandas.DataFrame.from_dict(results).set_index("date")
    assert isinstance(daily_df, pandas.DataFrame)
    return daily_df


def ying_kui_fen_bu(daily_df: pandas.DataFrame):
    """盈亏分布"""
    # 举例: 某次回测结果中, 有一天盈利200, 有一天亏损300, 其他天的盈亏均在这个区间内,
    # 则可以划一个范围, 比如: (-300,-200),(-200,-100),(-100,0),(0,100),(100,200)
    # 然后统计每个范围内有多少数据, 并展示出来, 这就是"盈亏分布"图,

    df: pandas.DataFrame = daily_df

    hist, x = numpy.histogram(df["net_pnl"], bins="auto")
    x = x[:-1]
    assert len(hist) == len(x)
    #    x: net_pnl 的取值范围,
    # hist: 这个范围内有多少个 net_pnl,

    from matplotlib import pyplot
    for i in range(0, len(hist), 1):
        pyplot.bar(x=x[i], height=hist[i])

    pyplot.title("ying_kui_fen_bu")
    pyplot.xlabel("net_pnl")
    pyplot.ylabel("count")
    pyplot.show()


if __name__ == "__main__":
    daily_results: dict = gen_daily_results()
    results: dict = gen_results(daily_results)
    daily_df: pandas.DataFrame = gen_daily_df(results)
    ying_kui_fen_bu(daily_df)


"""
点击"开始回测"
回测引擎启动了一个线程进行回测,
回测结束, 计算出来一个DataFrame【self.result_df = engine.calculate_result()】
然后发送了一个event【event: Event = Event(EVENT_BACKTESTER_BACKTESTING_FINISHED)】
这个event最后触发了一个回调函数"process_backtesting_finished_event"
这个回调函数拿到了DataFrame, 然后计算统计直方图(np.histogram), 然后把数据填入图表, 用于展示,
"""
